package co.gov.aerocivil.siga.comun.modelo.quejaaerolinea;

import java.io.Serializable;
import java.util.Date;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToOne;
import javax.persistence.SequenceGenerator;
import javax.persistence.Table;
import javax.validation.constraints.NotNull;

import org.hibernate.envers.Audited;

import co.gov.aerocivil.siga.comun.modelo.IEntidad;
import co.gov.aerocivil.siga.comun.modelo.administrador.Aerolinea;
import co.gov.aerocivil.siga.comun.modelo.administrador.Aeropuerto;
import co.gov.aerocivil.siga.comun.modelo.administrador.Ciudad;

import com.thoughtworks.xstream.annotations.XStreamAlias;

/**
 * @author oaortiz
 * @version 1.0
 * @created 22-oct-2013 03:42:29 p.m.
 */
@Entity
@Table(name = "QUE_VUELO")
@Audited
@XStreamAlias("VUELO")
public class Vuelo implements Serializable, IEntidad<Long> {

	/**
	 * Campo serial de la entidad
	 */
	private static final long serialVersionUID = 1L;

	/**
	 * Atributo id de la entidad {@link Vuelo} asociado con la columna ID_VUELO
	 * de la tabla QUE_VUELO
	 */
	@Id
	@SequenceGenerator(name = "QUE_VUELO_ID_GENERATOR", sequenceName = "SEQ_QUE_VUELO", allocationSize = 1)
	@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "QUE_VUELO_ID_GENERATOR")
	@Column(name = "ID_VUELO", unique = true, nullable = false, precision = 38)
	private Long id;

	/**
	 * Atributo fechaHechos de la entidad {@link Vuelo} asociado con la columna
	 * FECHA_HECHOS de la tabla QUE_VUELO
	 */
	@Column(name = "FECHA_HECHOS", nullable = false)
	@NotNull
	private Date fechaHechos;

	/**
	 * Atributo numeroVuelo de la entidad {@link Vuelo} asociado con la columna
	 * NUMERO_VUELO de la tabla QUE_VUELO
	 */
	@Column(name = "NUMERO_VUELO", nullable = false)
	@NotNull
	private String numeroVuelo;

	/**
	 * Atributo trayectoConexion de la entidad {@link Vuelo} asociado con la
	 * columna TRAYECTO_CONEXION de la tabla QUE_VUELO
	 */
	@Column(name = "TRAYECTO_CONEXION")
	private String trayectoConexion;

	/**
	 * Atributo aerolinea de la entidad {@link Vuelo} asociado con la columna
	 * ID_AEROLINEA de la tabla QUE_VUELO
	 */
	@ManyToOne(fetch = FetchType.EAGER, cascade = { CascadeType.DETACH,
			CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
	@JoinColumn(name = "ID_AEROLINEA")
	@NotNull
	private Aerolinea aerolinea;

	/**
	 * Atributo aeropuerto de la entidad {@link Vuelo} asociado con la columna
	 * ID_AEROPUERTO de la tabla QUE_VUELO
	 */
	@OneToOne(fetch = FetchType.EAGER, cascade = { CascadeType.DETACH,
			CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
	@JoinColumn(name = "ID_AEROPUERTO", nullable = false)
	@NotNull
	private Aeropuerto aeropuerto;

	/**
	 * Atributo aeropuertoOrigen de la entidad {@link Vuelo} asociado con la
	 * columna ID_AEROPUERTO_ORIGEN de la tabla QUE_VUELO
	 */
	@OneToOne(fetch = FetchType.EAGER, cascade = { CascadeType.DETACH,
			CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
	@JoinColumn(name = "ID_AEROPUERTO_ORIGEN", nullable = false)
	@NotNull
	private Aeropuerto aeropuertoOrigen;

	/**
	 * Atributo aeropuertoDestino de la entidad {@link Vuelo} asociado con la
	 * columna ID_AEROPUERTO_DESTINO de la tabla QUE_VUELO
	 */
	@OneToOne(fetch = FetchType.EAGER, cascade = { CascadeType.DETACH,
			CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
	@JoinColumn(name = "ID_AEROPUERTO_DESTINO", nullable = false)
	@NotNull
	private Aeropuerto aeropuertoDestino;

	/**
	 * Atributo ciudad de la entidad {@link Vuelo} asociado con la columna
	 * ID_CIUDAD de la tabla QUE_VUELO
	 */
	@ManyToOne(fetch = FetchType.EAGER, cascade = { CascadeType.DETACH,
			CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
	@JoinColumn(name = "ID_CIUDAD", nullable = false)
	@NotNull
	private Ciudad ciudad;

	/**
	 * Atributo queja de la entidad {@link Vuelo} asociado con la columna
	 * ID_QUEJA de la tabla QUE_VUELO
	 */
	@OneToOne(fetch = FetchType.EAGER, cascade = { CascadeType.DETACH,
			CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
	@JoinColumn(name = "ID_QUEJA", nullable = false)
	@NotNull
	private QuejaAerolinea queja;

	public Vuelo() {

	}

	/**
	 * @return la fecha de los hechos
	 */
	public Date getFechaHechos() {
		return fechaHechos;
	}

	/**
	 * @param fechaHechos
	 */
	public void setFechaHechos(final Date fechaHechos) {
		this.fechaHechos = fechaHechos;
	}

	/**
	 * @return el número de vuelo
	 */
	public String getNumeroVuelo() {
		return numeroVuelo;
	}

	/**
	 * @param numeroVuelo
	 */
	public void setNumeroVuelo(final String numeroVuelo) {
		this.numeroVuelo = numeroVuelo;
	}

	/**
	 * @return el trayecto de conexión
	 */
	public String getTrayectoConexion() {
		return trayectoConexion;
	}

	/**
	 * @param trayectoConexion
	 */
	public void setTrayectoConexion(final String trayectoConexion) {
		this.trayectoConexion = trayectoConexion;
	}

	/**
	 * @return la aerolínea
	 */
	public Aerolinea getAerolinea() {
		return aerolinea;
	}

	/**
	 * @param aerolinea
	 */
	public void setAerolinea(final Aerolinea aerolinea) {
		this.aerolinea = aerolinea;
	}

	/**
	 * @return el aeropuerto
	 */
	public Aeropuerto getAeropuerto() {
		return aeropuerto;
	}

	/**
	 * @param aeropuerto
	 */
	public void setAeropuerto(final Aeropuerto aeropuerto) {
		this.aeropuerto = aeropuerto;
	}

	/**
	 * @return el aeropuerto de origen
	 */
	public Aeropuerto getAeropuertoOrigen() {
		return aeropuertoOrigen;
	}

	/**
	 * @param aeropuertoOrigen
	 */
	public void setAeropuertoOrigen(final Aeropuerto aeropuertoOrigen) {
		this.aeropuertoOrigen = aeropuertoOrigen;
	}

	/**
	 * @return el aeropuerto de destino
	 */
	public Aeropuerto getAeropuertoDestino() {
		return aeropuertoDestino;
	}

	/**
	 * @param aeropuertoDestino
	 */
	public void setAeropuertoDestino(final Aeropuerto aeropuertoDestino) {
		this.aeropuertoDestino = aeropuertoDestino;
	}

	/**
	 * @return la ciudad
	 */
	public Ciudad getCiudad() {
		return ciudad;
	}

	/**
	 * @param ciudad
	 */
	public void setCiudad(final Ciudad ciudad) {
		this.ciudad = ciudad;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see co.gov.aerocivil.siga.comun.modelo.IEntidad#getId()
	 */
	@Override
	public Long getId() {
		return id;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * co.gov.aerocivil.siga.comun.modelo.IEntidad#setId(java.io.Serializable)
	 */
	@Override
	public void setId(final Long id) {
		this.id = id;
	}

	/**
	 * @return la queja
	 */
	public QuejaAerolinea getQueja() {
		return queja;
	}

	/**
	 * @param queja
	 */
	public void setQueja(final QuejaAerolinea queja) {
		this.queja = queja;
	}

	@Override
	public String toString() {
		return "Vuelo [aeropuertoOrigen=" + aeropuertoOrigen
				+ ", aeropuertoDestino=" + aeropuertoDestino;
	}

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = (prime * result)
				+ ((aerolinea == null) ? 0 : aerolinea.hashCode());
		result = (prime * result)
				+ ((aeropuerto == null) ? 0 : aeropuerto.hashCode());
		result = (prime * result)
				+ ((aeropuertoDestino == null) ? 0 : aeropuertoDestino
						.hashCode());
		result = (prime * result)
				+ ((aeropuertoOrigen == null) ? 0 : aeropuertoOrigen.hashCode());
		result = (prime * result) + ((ciudad == null) ? 0 : ciudad.hashCode());
		result = (prime * result)
				+ ((fechaHechos == null) ? 0 : fechaHechos.hashCode());
		result = (prime * result) + ((id == null) ? 0 : id.hashCode());
		result = (prime * result)
				+ ((numeroVuelo == null) ? 0 : numeroVuelo.hashCode());
		result = (prime * result) + ((queja == null) ? 0 : queja.hashCode());
		result = (prime * result)
				+ ((trayectoConexion == null) ? 0 : trayectoConexion.hashCode());
		return result;
	}

	@Override
	public boolean equals(final Object obj) {
		if (this == obj) {
			return true;
		}
		if (obj == null) {
			return false;
		}
		if (getClass() != obj.getClass()) {
			return false;
		}
		Vuelo other = (Vuelo) obj;
		if (aerolinea == null) {
			if (other.aerolinea != null) {
				return false;
			}
		} else if (!aerolinea.equals(other.aerolinea)) {
			return false;
		}
		if (aeropuerto == null) {
			if (other.aeropuerto != null) {
				return false;
			}
		} else if (!aeropuerto.equals(other.aeropuerto)) {
			return false;
		}
		if (aeropuertoDestino == null) {
			if (other.aeropuertoDestino != null) {
				return false;
			}
		} else if (!aeropuertoDestino.equals(other.aeropuertoDestino)) {
			return false;
		}
		if (aeropuertoOrigen == null) {
			if (other.aeropuertoOrigen != null) {
				return false;
			}
		} else if (!aeropuertoOrigen.equals(other.aeropuertoOrigen)) {
			return false;
		}
		if (ciudad == null) {
			if (other.ciudad != null) {
				return false;
			}
		} else if (!ciudad.equals(other.ciudad)) {
			return false;
		}
		if (fechaHechos == null) {
			if (other.fechaHechos != null) {
				return false;
			}
		} else if (!fechaHechos.equals(other.fechaHechos)) {
			return false;
		}
		if (id == null) {
			if (other.id != null) {
				return false;
			}
		} else if (!id.equals(other.id)) {
			return false;
		}
		if (numeroVuelo == null) {
			if (other.numeroVuelo != null) {
				return false;
			}
		} else if (!numeroVuelo.equals(other.numeroVuelo)) {
			return false;
		}
		if (queja == null) {
			if (other.queja != null) {
				return false;
			}
		} else if (!queja.equals(other.queja)) {
			return false;
		}
		if (trayectoConexion == null) {
			if (other.trayectoConexion != null) {
				return false;
			}
		} else if (!trayectoConexion.equals(other.trayectoConexion)) {
			return false;
		}
		return true;
	}

}